package utils;

import java.lang.reflect.Constructor;
import java.lang.reflect.Field;
import java.lang.reflect.InvocationTargetException;
import java.util.*;
import java.util.jar.Attributes;

public class TransDataUtil {
    /**
     * 将指定的Map集合封装到具体的类对象中
     * @param map 指定的类字段的集合
     * @param c 对应的类的Class对象
     * @param <T> 对应的类的类型
     * @return 具体的类的实例
     */
    public static <T> T transMapToModel(Map<String , Object> map , Class<T> c  )  {
        try {
            // 创建 实例对象
            Constructor<T> constructor = c.getConstructor() ;
            constructor.setAccessible( true );
            T object = constructor.newInstance() ;
            Class superClass = c ;
            // 获取对应的类的所有字段
            ArrayList<Field> fieldNames = new ArrayList<>() ;
            while( Objects.nonNull( superClass)&& !superClass.getName().equalsIgnoreCase("java.lang.object")){
                fieldNames.addAll(Arrays.asList(c.getDeclaredFields() ) ) ;
                superClass = c.getSuperclass();
            }
            // 通过遍历 进行操作
            for( Field f : fieldNames){
                f.setAccessible( true );
                if( map.containsKey( f.getName() )){
                    f.set( object , map.get( f.getName() ));
                }
            }
            return object ;
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
        } catch (InstantiationException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            e.printStackTrace();
        }
        return null ;
    }

    /**
     * 将指定的对象放入到Map中
     * @param o 指定的对象
     * @return Map&lt;String , Object &gt;K是对应的属性名，V是对应的属性值
     */
    public static Map<String , Object> transModelToMap( Object o ){
        Map<String , Object> map = new HashMap<>() ;
        ArrayList<Field> fields = new ArrayList<>() ;
        Class c = o.getClass() ;
        while( Objects.nonNull( c ) && !c.getName().equalsIgnoreCase("java.lang.object") ){
            fields.addAll( Arrays.asList( c.getDeclaredFields() )) ;
            c = c.getSuperclass() ;
        }
        try {
            for( Field f : fields ){
                f.setAccessible( true );
                if( !f.getName().equalsIgnoreCase("serialVersionUID")) {
                    map.put(f.getName(), f.get(o));
                }
            }
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
        return map ;
    }
}
